﻿using UnityEngine;
using System.IO;
using System.Security.Cryptography;
using System.Text;


namespace Framework.AssetsManager
{ 
    public class LoadTask
    {
        private string m_name;
        private string m_path;
        private EResType m_type;
        private ELoadTaskType m_loadType;
        private int m_version;
        private string m_MD5;

        private ELoadTaskState m_state;
        private NetLoader m_loader;
        private float m_progress = 0.0f;

        public LoadTask(string _name, string _path, EResType _type, ELoadTaskType _loadType, int _version, string MD5)
        {
            m_name = _name;
            m_path = _path;
            m_type = _type;
            m_loadType = _loadType;
            m_version = _version;
            m_MD5 = MD5;
        }

        ~LoadTask()
        { }


        public string name
        {
            get { return m_name; }
        }

        public string path
        {
            get { return m_path; }
        }

        public EResType type
        {
            get { return m_type; }
        }

        public ELoadTaskType loadType
        {
            get { return m_loadType; }
        }

        public ELoadTaskState loadState
        {
            get { return m_state; }
        }

        public float progress
        {
            get { return m_progress; }
        }


        public void Start()
        {
            if (m_loadType == ELoadTaskType.WEB)
            {
                m_loader = new NetLoader(m_path);
                m_loader.OnLoaderError = OnError;
                m_loader.OnLoaderProcess = OnProcess;
                m_loader.OnLoaderFinish = OnFinish;
                m_loader.Load(false);

                m_state = ELoadTaskState.LOADING;
            }
        }

        private void OnError(string _error)
        {
            Debug.LogError(_error+":load "+ path);
            m_state = ELoadTaskState.FAILED;
        }

        private void OnFinish(WWW _www, AssetBundle _ab)
        {
            string savePath = Application.persistentDataPath + "/res" + AssetsMgtConst.CurrentVersion + "/";

            MD5 md5 = new MD5CryptoServiceProvider();
            byte[] retVal = md5.ComputeHash(_www.bytes);
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < retVal.Length; i++)
            {
                sb.Append(retVal[i].ToString("x2"));
            }
            string downloadMD5 = sb.ToString();
            if(downloadMD5 != m_MD5)
            {
                m_state = ELoadTaskState.FAILED;
                return;
            }

            if (!Directory.Exists(savePath))
            {
                Directory.CreateDirectory(savePath);
            }

            if(File.Exists(savePath + m_name))
            {
                File.Delete(savePath + m_name);
            }

            FileStream cache = new FileStream(savePath + m_name, FileMode.CreateNew);
            cache.Write(_www.bytes, 0, _www.bytes.Length);
            cache.Close();

            if(_ab != null)
            {
                ResManager.Instance.AddResource(m_name, EResType.ASSETBUNDLE, _ab);
                float cacheTime = Config.ABCacheTime;
                ABCache abCache = new ABCache(m_name, Config.ABCacheTime, _ab);
                ABCacheTimer.Instance.AddABCache(abCache);
            }

            m_state = ELoadTaskState.SUCCESS;
            m_progress = 1.0f;
        }

        private void OnProcess(float _progress)
        {
            m_progress = _progress;
        }

        public void Unload()
        {
            if (m_loader != null)
            {
                if (m_loader.www != null)
                {
                    m_loader.www.Dispose();
                }
            }
        }
    }

}
